package opf5.ui;

import java.awt.EventQueue;
import java.util.ArrayList;
import java.util.List;

import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JButton;
import javax.swing.JOptionPane;
import javax.swing.JTextField;
import javax.swing.ListSelectionModel;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;

import opf5.casosDeUso.LoginDependiente;
import opf5.entities.calificaciones.CalificacionConcreta;
import opf5.entities.dominio.Calificacion;
import opf5.entities.dominio.Inscripcion;
import opf5.entities.dominio.Jugador;
import opf5.entities.dominio.Partido;
import opf5.entities.repositorios.OPF5Factory;
import opf5.entities.repositorios.RepositorioPartidos;

import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;

public class VistaCalificarJugador extends LoginDependiente {

	private JFrame frame;
	private OPF5TablaPartidos tablaPartidos;
	private OPF5TablaJugadores tablaJugadores;
	private JTextField textCalificacion;
	private JTextField textComentario;
	private RepositorioPartidos repositorioPartidos;
	private List<Partido> partidos;
	private Partido partido;
	private List<Jugador> jugadoresCalificables;
	private JButton btnCalificar;
	private Jugador jugadorElegido;

	public VistaCalificarJugador(RepositorioPartidos repositorioPartidos) {
		this.repositorioPartidos = repositorioPartidos;
	}

	/**
	 * Initialize the contents of the frame.
	 * @wbp.parser.entryPoint
	 */
	public void initialize() {
		frame = new JFrame();
		frame.setBounds(100, 100, 645, 346);
		frame.getContentPane().setLayout(null);
		
		JLabel lblCalificarJugador = new JLabel("Calificar Jugador");
		lblCalificarJugador.setBounds(12, 12, 109, 15);
		frame.getContentPane().add(lblCalificarJugador);
		
		tablaPartidos = new OPF5TablaPartidos(new String[] {"Fecha", "Lugar", "Inscriptos"});
		tablaPartidos.setBounds(22, 39, 309, 169);
		frame.getContentPane().add(tablaPartidos);
		
		ListSelectionModel listSelectionModel = tablaPartidos.table.getSelectionModel();
	    listSelectionModel.addListSelectionListener(new ListSelectionListener() {
			@Override
			public void valueChanged(ListSelectionEvent arg0) {
				cargarJugadores();
			} 	
	    });
		
		tablaJugadores = new OPF5TablaJugadores();
		tablaJugadores.setBounds(343, 39, 279, 169);
		frame.getContentPane().add(tablaJugadores);
		
		ListSelectionModel listSelectionModeljugadores = tablaJugadores.table.getSelectionModel();
		listSelectionModeljugadores.addListSelectionListener(new ListSelectionListener() {
			@Override
			public void valueChanged(ListSelectionEvent arg0) {
				verificarCalificacion();
			} 	
	    });
		
		btnCalificar = new JButton("Calificar");
		btnCalificar.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				runCalificarJugador();
			}
		});
		btnCalificar.setBounds(515, 272, 107, 25);
		frame.getContentPane().add(btnCalificar);
		
		JLabel lblCalificacion = new JLabel("Calificacion:");
		lblCalificacion.setBounds(20, 222, 72, 15);
		frame.getContentPane().add(lblCalificacion);
		
		JLabel lblComentario = new JLabel("Comentario:");
		lblComentario.setBounds(20, 247, 72, 15);
		frame.getContentPane().add(lblComentario);
		
		textCalificacion = new JTextField();
		textCalificacion.setBounds(102, 219, 43, 19);
		frame.getContentPane().add(textCalificacion);
		textCalificacion.setColumns(10);
		
		textComentario = new JTextField();
		textComentario.setBounds(102, 244, 168, 19);
		frame.getContentPane().add(textComentario);
		textComentario.setColumns(10);

		cargarDatos();
		
		final VistaCalificarJugador window = this;
		EventQueue.invokeLater(new Runnable() {
			public void run() {
				try {
					window.frame.setVisible(true);
				} catch (Exception e) {
					e.printStackTrace();
				}
			}
		});

	}

	protected void runCalificarJugador() {
		if (! datosValidos()) {
			JOptionPane.showMessageDialog(frame, "Debe seleccionar un jugador y especificar una nota valida.");
			return;
		}
		
		jugadorElegido.agregarCalificacion(OPF5Factory.getInstance().makeCalificacion(
				jugador,
				partido,
				new Integer(textCalificacion.getText()),
				textComentario.getText()));
		
		JOptionPane.showMessageDialog(frame, "El jugador fue calificado.");
		verificarCalificacion();
		VistaDatosJugador.getInstance().initialize(jugadorElegido);
		this.cargarJugadores();
	}

	private boolean datosValidos() {
		return  this.textCalificacion.getText().matches("[0-9]{1,2}") &&
				new Integer(this.textCalificacion.getText()) <= 10 &&
				new Integer(this.textCalificacion.getText()) > 0 &&
				this.tablaPartidos.getIndice() >= 0 &&
				this.tablaJugadores.getIndice() >= 0;
	}

	protected void verificarCalificacion() {
		if (tablaJugadores.getIndice() < 0)
			return;
		
		jugadorElegido = jugadoresCalificables.get(tablaJugadores.getIndice());
		if (jugadorElegido.fueCalificadoPor(jugador, partido)) {
			deshabilitarModificacion();
			cargarCalificacionHecha();
		} else {
			habilitarModificacion();
		}
	}

	private void cargarCalificacionHecha() {
		Calificacion calificacion = jugadorElegido.getCalificacion(jugador, partido);
		this.textCalificacion.setText(Integer.toString(calificacion.getNota()));
		this.textComentario.setText(calificacion.getComentario());
	}

	private void habilitarModificacion() {
		this.textCalificacion.setEnabled(true);
		this.textCalificacion.setText("");
		this.textComentario.setEnabled(true);
		this.textComentario.setText("");
		this.btnCalificar.setEnabled(true);
	}

	private void deshabilitarModificacion() {
		this.textCalificacion.setEnabled(false);
		this.textComentario.setEnabled(false);
		this.btnCalificar.setEnabled(false);
	}

	protected void cargarJugadores() {
		if (tablaPartidos.getIndice() < 0) {
			return;
		}
		
		partido = partidos.get(tablaPartidos.getIndice());
		jugadoresCalificables = new ArrayList<Jugador>();
		
		for (Inscripcion i : partido.getInscripciones()) {
			if (! i.getJugador().equals(jugador))
				jugadoresCalificables.add(i.getJugador());
		}
		
		this.tablaJugadores.cargarJugadoresModelo(jugadoresCalificables);
	}

	private void cargarDatos() {
		partidos = this.repositorioPartidos.getPartidosJugadosPor(this.jugador);
		this.tablaPartidos.cargarPartidosModelo(partidos);
	}
}
